/******************************************************************
 * Copyright (c) 2024 Bocloud Technologies Co., Ltd.
 * installer is licensed under Mulan PSL v2.
 * You can use this software according to the terms and conditions of the Mulan PSL v2.
 * You may obtain n copy of Mulan PSL v2 at:
 *          http://license.coscl.org.cn/MulanPSL2
 * THIS SOFTWARE IS PROVIDED ON AN "AS IS" BASIS, WITHOUT WARRANTIES OF ANY KIND,
 * EITHER EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO NON-INFRINGEMENT,
 * MERCHANTABILITY OR FIT FOR A PARTICULAR PURPOSE.
 * See the Mulan PSL v2 for more details.
 ******************************************************************/

package cmd

import (
	"fmt"
	"os"
	"strings"
	"text/tabwriter"

	"github.com/spf13/cobra"
	configinit "gopkg.openfuyao.cn/bkecommon/cluster/initialize"
	"gopkg.openfuyao.cn/bkecommon/ntp/sntp"

	econd "gopkg.openfuyao.cn/bkeadm/pkg/executor/containerd"
	"gopkg.openfuyao.cn/bkeadm/pkg/global"
	"gopkg.openfuyao.cn/bkeadm/pkg/infrastructure"
	"gopkg.openfuyao.cn/bkeadm/utils"
)

// statusCmd Displays the status of the local service started by bke.
var statusCmd = &cobra.Command{
	Use:   "status",
	Short: "Displays the status of the local service started by bke.",
	Long:  `Displays the status of the local service started by bke.`,
	Example: `
# Displays the status of the local service started by bke.
bke status
`,
	Run: func(cmd *cobra.Command, args []string) {
		display()
	},
}

func init() {
	rootCmd.AddCommand(statusCmd)
}

func display() {
	headers := []string{"server", "name", "default", "status", "mount"}
	var rows [][]string

	containerServers := [][]string{
		{"container", utils.LocalKubernetesName, fmt.Sprintf("tcp://0.0.0.0:%s", utils.DefaultKubernetesPort), "notCreated", ""},
		{"container", utils.LocalImageRegistryName, fmt.Sprintf("tcp://0.0.0.0:%s", configinit.DefaultImageRepoPort), "notCreated", fmt.Sprintf("%s/%s", global.Workspace, utils.ImageDataDirectory)},
		{"container", utils.LocalYumRegistryName, fmt.Sprintf("tcp://0.0.0.0:%s", configinit.DefaultYumRepoPort), "notCreated", fmt.Sprintf("%s/%s", global.Workspace, utils.SourceDataDirectory)},
		{"container", utils.LocalChartRegistryName, fmt.Sprintf("tcp://0.0.0.0:%s", utils.DefaultChartRegistryPort), "notCreated", fmt.Sprintf("%s/%s", global.Workspace, utils.ChartDataDirectory)},
		{"container", utils.LocalNFSRegistryName, fmt.Sprintf("tcp://0.0.0.0:2049"), "notCreated", fmt.Sprintf("%s/%s", global.Workspace, utils.NFSDataDirectory)},
	}
	procServers := [][]string{
		{"proc", "ntpserver", fmt.Sprintf("udp://0.0.0.0:%d", utils.DefaultNTPServerPort), "notCreated", ""},
	}

	if infrastructure.IsDocker() {
		for _, server := range containerServers {
			newServer := server
			if info, ok := global.Docker.ContainerExists(server[1]); ok {
				newServer[0] = "docker"
				newServer[3] = info.State.Status
			}
			rows = append(rows, newServer)
		}
	}

	if infrastructure.IsContainerd() {
		for _, server := range containerServers {
			newServer := server
			newServer[0] = "containerd"
			newServer[3] = "notCreated"
			if info, err := econd.ContainerInspect(server[1]); err == nil && len(info.Id) > 0 {
				newServer[3] = info.State.Status
			}
			rows = append(rows, newServer)
		}
	}

	for _, server := range procServers {
		newServer := server
		if server[1] == "ntpserver" {
			_, err := sntp.Client(fmt.Sprintf("127.0.0.1:%d", utils.DefaultNTPServerPort))
			if err == nil {
				newServer[3] = "running"
			}
			if utils.Exists("/etc/systemd/system/ntpserver.service") {
				newServer[0] = "systemd"
			}
			rows = append(rows, newServer)
		}
	}
	const tabPadding = 2 // 列之间的最小空格数，用于tabwriter对齐
	w := tabwriter.NewWriter(os.Stdout, 0, 0, tabPadding, ' ', 0)
	fmt.Fprintln(w, strings.Join(headers, "\t"))
	for _, row := range rows {
		fmt.Fprintln(w, strings.Join(row, "\t"))
	}
	err := w.Flush()
	if err != nil {
		fmt.Println("flush tablewriter failed:", err.Error())
	}
}
